package LUCKY.Android;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import org.json.JSONArray;
import org.json.JSONObject;


import LUCKY.Android.Util.DirectionsJSONParser;
import LUCKY.Android.Util.FunctionsUtil;
import android.app.AlertDialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.res.Configuration;
import android.graphics.Color;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.support.v4.app.FragmentActivity;
import android.text.Html;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.widget.Toast;


import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.GoogleMap.OnMapClickListener;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
import com.google.android.gms.maps.model.PolylineOptions;

public class mapagooglev2 extends FragmentActivity 
implements OnMapClickListener {
	private LatLng EQUIPO = null;
	private GoogleMap mapa;
	protected Context m_context; 
	private LatLng UBiACTUAL;
	String modo = "driving";
	String language_modo = "es";
	CharSequence[] values = null;
	private double m_latitud;
	private double m_longitud;
	private Handler handler;
	ProgressDialog progressDialog;
	
	@Override
	public void onConfigurationChanged(Configuration newConfig) {
		super.onConfigurationChanged(newConfig);
	}
	
	
	@Override 
	protected void onCreate(Bundle savedInstanceState) {
	super.onCreate(savedInstanceState);
	setContentView(R.layout.mapagooglev2);
	m_context = getApplicationContext();
	m_latitud=Double.parseDouble(getIntent().getStringExtra("latitud"));
	m_longitud=Double.parseDouble(getIntent().getStringExtra("longitud"));
	EQUIPO = new LatLng(m_latitud,m_longitud);
	mapa = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map)).getMap();
	
	mapa.setMapType(GoogleMap.MAP_TYPE_NORMAL);
	mapa.moveCamera(CameraUpdateFactory.newLatLngZoom(EQUIPO, 15));
	mapa.setMyLocationEnabled(true);
	mapa.getUiSettings().setZoomControlsEnabled(false);
	mapa.getUiSettings().setCompassEnabled(true);
	mapa.addMarker(new MarkerOptions()
	.position(EQUIPO)
	.title("EQUIPO")
	.snippet("Ubicacion del Equipo")
	.icon(BitmapDescriptorFactory
	.fromResource(R.drawable.googlemapsiconblankhi))
	.anchor(0.5f, 0.5f));
	mapa.setOnMapClickListener(this);
	
	//obtenerubicacionactual();
	}
	

	private void moveCamera() {
		mapa.moveCamera(CameraUpdateFactory.newLatLng(EQUIPO));
	}
	
	private void animateCamera() {
		if (mapa.getMyLocation() != null)
		mapa.animateCamera(CameraUpdateFactory.newLatLngZoom(
				new LatLng( mapa.getMyLocation().getLatitude(),                                         
		mapa.getMyLocation().getLongitude()), 15));
	}
		
	private void obtenerubicacionactual() {
		mapa.addMarker(new MarkerOptions().position(
		new LatLng(mapa.getCameraPosition().target.latitude,
		mapa.getCameraPosition().target.longitude)));
	}

	private void addruta() {
	 progressDialog = ProgressDialog.show(mapagooglev2.this, "Buscando Ruta", "Por favor espere...", true);
        

		handler = new Handler();
		
		final Runnable runInUIThread = new Runnable() {
            public void run() {
            
		LatLng origin = UBiACTUAL;
	     LatLng dest = EQUIPO;
	
	     if (UBiACTUAL == null)
	     {
	 		UBiACTUAL = new LatLng(mapa.getMyLocation().getLatitude(),mapa.getMyLocation().getLongitude());		 		
	    	 origin = UBiACTUAL;
	     }
	    	 // Getting URL to the Google Directions API
	         String url = getDirectionsUrl(origin, dest, modo);
	         DownloadTask downloadTask = new DownloadTask();
	         // Start downloading json data from Google Directions API
	         downloadTask.execute(url);
            }
        };
		
        new Thread() {
             @Override
             public void run() {
            	 handler.postDelayed(runInUIThread,1000);
                
                }
            }.start();
        
        	}
	
	
	//Fetches data from url passed
	private class DownloadTask extends AsyncTask<String, Void, String>{
	
	    // Downloading data in non-ui thread
	    @Override
	    protected String doInBackground(String... url) {
	
	        // For storing data from web service
	
	        String data = "";
	
	        try{
	            // Fetching the data from web service
	             data = downloadUrl(url[0]);
	        }catch(Exception e){
	        //    Log.d("Background Task",e.toString());
	        }
	        return data;
	    }
	
	    // Executes in UI thread, after the execution of
	    // doInBackground()
	    @Override
	    protected void onPostExecute(String result) {
	        super.onPostExecute(result);
	
	        ParserTask parserTask = new ParserTask();
	try {
		  // Invokes the thread for parsing the JSON data
	    parserTask.execute(result);
	} catch (Exception e) {
		// TODO: handle exception
	}
	      
	    }
	}
	
	
	/** A method to download json data from url */
	private String downloadUrl(String strUrl) throws IOException{
	    String data = "";
	    InputStream iStream = null;
	    HttpURLConnection urlConnection = null;
	    try{
	        URL url = new URL(strUrl);
	
	        // Creating an http connection to communicate with url
	        urlConnection = (HttpURLConnection) url.openConnection();
	       // urlConnection.setRequestProperty("Accept-Charset", "UTF-8");

	        // Connecting to url
	        urlConnection.connect();
	
	        // Reading data from url
	        iStream = urlConnection.getInputStream();
	
	        BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
	
	        StringBuffer sb  = new StringBuffer();
	
	        String line = "";
	        while( ( line = br.readLine())  != null){
	            sb.append(line);
	        }
	
	        data = sb.toString();
	
	        br.close();
	
	    }catch(Exception e){
	   //     Log.d("Exception while downloading url", e.toString());
	    }finally{
	        iStream.close();
	        urlConnection.disconnect();
	    }
	    return data;
	}
	
	
	/** A class to parse the Google Places in JSON format */
	private class ParserTask extends AsyncTask<String, Integer, List<List<HashMap<String,String>>> >{
	
	    // Parsing the data in non-ui thread
	    @Override
	    protected List<List<HashMap<String, String>>> doInBackground(String... jsonData) {
	
	    JSONObject jObject;
	    List<List<HashMap<String, String>>> routes = null;
	
	        try{
                jObject = new JSONObject(jsonData[0]);
	            DirectionsJSONParser parser = new DirectionsJSONParser();
	
	          
	            JSONArray routeObject = jObject.getJSONArray("routes"); // pull out the "route" object
	            // no routes found
	            if (routeObject.length() == 0) {
	               
	               
	            }
	            else
	            {
	            	       JSONArray arrLegs = routeObject.getJSONObject(0).getJSONArray("legs");
	            JSONObject firstLeg = arrLegs.getJSONObject(0);
	            JSONArray arrSteps = firstLeg.getJSONArray("steps");
	            int len = arrSteps.length();
	            JSONObject leg = null;
	            
	            try {
	            	
	            	for(int l=0;l<values.length;l++){
	            		values [l]=null;
	            		}
				} catch (Exception e) {
					// TODO: handle exception
				}
	            
	            values = new String[len];
	            // get instructions
	            for (int i = 0; i < len; ++i) {
	                leg = arrSteps.getJSONObject(i);
	                // location = leg.getJSONObject("start_location");
	                String encoded = leg.getJSONObject("polyline").getString("points");
	                values[i] = (i+1)+": "+ Html.fromHtml(leg.getString("html_instructions"));
	                
	                Log.d("html_instructions", "" + Html.fromHtml(leg.getString("html_instructions")));
	           
	            }
	           
	            }
	            
	     
	            
	            
	            
	            
	            
	            /* JSONArray durationObject = jsonObject.getJSONArray("duration"); // pull out the "duration" object
	           // String duration = durationObject.getString("text"); //this should be the duration text value (20 hours 40 mins)
	            */
	            // Starts parsing data
	            routes = parser.parse(jObject);
	            progressDialog.dismiss();
	        }catch(Exception e){
	            e.printStackTrace();
	            progressDialog.dismiss();
	        }
	        return routes;
	    }
	
	    // Executes in UI thread, after the parsing process
	    @Override
	    protected void onPostExecute(List<List<HashMap<String, String>>> result) {
	    	   super.onPreExecute ();
	        ArrayList<LatLng> points = null;
	        PolylineOptions lineOptions = null;
	
	        // Traversing through all the routes
	        for(int i=0;i<result.size();i++){
	            points = new ArrayList<LatLng>();
	            lineOptions = new PolylineOptions();
	
	            // Fetching i-th route
	            List<HashMap<String, String>> path = result.get(i);
	
	            // Fetching all the points in i-th route
	            for(int j=0;j<path.size();j++){
	                HashMap<String,String> point = path.get(j);
	
	                double lat = Double.parseDouble(point.get("lat"));
	                double lng = Double.parseDouble(point.get("lng"));
	                LatLng position = new LatLng(lat, lng);
	
	                points.add(position);
	            }
	
	            // Adding all the points in the route to LineOptions
	            lineOptions.addAll(points);
	            lineOptions.width(4);
	            if(modo.equals("driving"))
	            {
	            	lineOptions.color(Color.RED);	
	            }
	            if(modo.equals("walking"))
	            {  
	            	lineOptions.color(Color.GREEN);	
	            }
	            if(modo.equals("transit"))
	            {  
	            	lineOptions.color(Color.BLUE);	
	            }
	        }
	
	         // Drawing polyline in the Google Map for the i-th route
	         mapa.addPolyline(lineOptions);
	     }
	}
	
	private String getDirectionsUrl(LatLng origin,LatLng dest,String modo){
		 
	    // Origin of route
	    String str_origin = "origin="+origin.latitude+","+origin.longitude;
	
	    // Destination of route
	    String str_dest = "destination="+dest.latitude+","+dest.longitude;
	
	    // Sensor enabled
	    String sensor = "sensor=false";
	
	    String mode = "mode="+modo;
	    
	    String language = "language="+language_modo;
	     
	    // Waypoints
	    String waypoints = "";
	    
	    for(int i=2;i<2;i++){
	    	 LatLng point ;
	    	
	    	if (i == 1)
	    	{
	    		  point  = (LatLng) UBiACTUAL;
	    	}
	    	else
	    	{
	    		  point  = (LatLng) EQUIPO;
	    	}
	       
	        if(i==2)
	            waypoints = "waypoints=";
	        waypoints += point.latitude + "," + point.longitude + "|";
	    }
	    
	    
	    // Building the parameters to the web service
	    String parameters = str_origin+"&"+str_dest+"&"+sensor+"&"+waypoints+"&"+mode+"&"+language;
	
	    // Output format
	    String output = "json";
	
	    // Building the url to the web service
	    String url = "https://maps.googleapis.com/maps/api/directions/"+output+"?"+parameters;
	
	    return url;
	}
	
	@Override
	public void onMapClick(LatLng puntoPulsado) {
	/*mapa.addMarker(new MarkerOptions().position(puntoPulsado).
	icon(BitmapDescriptorFactory
	.defaultMarker(BitmapDescriptorFactory.HUE_YELLOW)));*/
	}
	


	 @Override
		public boolean onCreateOptionsMenu(Menu menu) {
			MenuInflater inflater = getMenuInflater();
			inflater.inflate(R.menu.mapgooglev2, menu);

			return true;
		}
	
	 @Override
		public boolean onOptionsItemSelected(MenuItem item) {
			// Handle item selection
			switch (item.getItemId()) {
			case R.id.mnu_ir_equipo:
				moveCamera();
					return true;
			case R.id.mnu_ubicacion_actual:
				
				animateCamera();
				return true;
			case R.id.mnu_indicacion:
			   
			    if (values == null )
			    {
			    	 FunctionsUtil.ShowMessage("DEBE DE SELECCIONAR UNA RUTA",Toast.LENGTH_LONG);
			    }
			    else
			    {
			    	showDialogButtonClickIndicacioones();
			    }
				
				// addruta();
				return true;
			case R.id.mnu_tipo_mapa:
				showDialogButtonClickMapa();
				
				return true;
			case R.id.mnu_tipo_ruta:
				showDialogButtonClickRuta();
	            return true;
			default:
				return false;
			}
		}
	
	
	
	
	
	    private void showDialogButtonClickMapa() {
	    	final CharSequence[] items = {"TERRAIN", "SATELLITE", "HYBRID", "NORMAL"};
	    	 
	    	AlertDialog.Builder builder = new AlertDialog.Builder(this);
	    	builder.setTitle("SELECCIONE TIPO DE MAPA A VISUALIZAR");
	    	builder.setSingleChoiceItems(items, -1, new DialogInterface.OnClickListener() {
	    	    public void onClick(DialogInterface dialog, int item) {
	    	    	if (item == 0)
	    	    	{
	    	    		mapa.setMapType(GoogleMap.MAP_TYPE_TERRAIN);
	    	    	}
	    	    	if (item == 1)
	    	    	{
	    	    		mapa.setMapType(GoogleMap.MAP_TYPE_SATELLITE);
	    	    	}
	    	    	if (item == 2)
	    	    	{
	    	    		mapa.setMapType(GoogleMap.MAP_TYPE_HYBRID);
	    	    	}
	    	    	if (item == 3)
	    	    	{
	    	    		mapa.setMapType(GoogleMap.MAP_TYPE_NORMAL);
	    	    	}
	    	        Toast toast = Toast.makeText(getApplicationContext(), "Haz elegido la opcion: " + items[item] , Toast.LENGTH_SHORT);
	    	        toast.show();
	    	        dialog.cancel();
	    	    }
	    	});
	    	AlertDialog alert = builder.create();
	    	alert.show();
	    }
	
	
	    private void showDialogButtonClickRuta() {
	    	final CharSequence[] items = {"AUTOMOVIL", "A PIE"
	    			//, "TRANSPORTE PUBLICO"
	    			//, "BICICLETA"
	    			};
	    	 
	    	AlertDialog.Builder builder = new AlertDialog.Builder(this);
	    	builder.setTitle("SELECCIONE TIPO DE RUTA A VISUALIZAR");
	    	builder.setSingleChoiceItems(items, -1, new DialogInterface.OnClickListener() {
	    	    public void onClick(DialogInterface dialog, int item) {
	    	    	if (item == 0)
	    	    	{
	    	    		modo = "driving";
	    	    		addruta();
	    	    	}
	    	    	if (item == 1)
	    	    	{
	    	    		modo = "walking";
	    	    		addruta();
	    	    	}
	    	    	if (item == 2)
	    	    	{
	    	    		modo = "transit";
	    	    		addruta();
	    	    	}
	    	    	
	    	    	if (item == 3)
	    	    	{
	    	    		modo = "BiCycling";
	    	    		addruta();
	    	    	}
	    	    	
	    	    	
	    	    	
	    	        Toast toast = Toast.makeText(getApplicationContext(), "Haz elegido la opcion: " + items[item] , Toast.LENGTH_SHORT);
	    	        toast.show();
	    	        dialog.cancel();
	    	    }
	    	});
	    	AlertDialog alert = builder.create();
	    	alert.show();
	    }
	
	
	
	   
	    private void showDialogButtonClickIndicacioones() {
	    			    	 
	    	AlertDialog.Builder builder3=new AlertDialog.Builder(this);
	    	builder3.setTitle("INDICACIONES").setItems(values, new DialogInterface.OnClickListener() {

	    	    public void onClick(DialogInterface dialog, int item) {
  	    	
	    	       
	    	    }
	    	});
	    	AlertDialog alert = builder3.create();
	    	alert.show();
	    }
	
	
	
	
	
	
}